package com.china.produce.controller;

import com.alibaba.excel.EasyExcel;
import com.alibaba.excel.ExcelWriter;
import com.alibaba.excel.support.ExcelTypeEnum;
import com.alibaba.excel.write.metadata.WriteSheet;
import com.alibaba.excel.write.metadata.style.WriteCellStyle;
import com.alibaba.excel.write.metadata.style.WriteFont;
import com.alibaba.excel.write.style.HorizontalCellStyleStrategy;
import com.china.produce.handler.MonthSheetWriteHandler;
import com.china.produce.pojo.User;
import com.china.produce.pojo.easyExcel.PileCheckMonthDto;
import com.china.produce.pojo.excel.Member;
import com.china.produce.pojo.excel.OrderData;
import com.china.produce.strategy.excel.CustomMergeStrategy;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import org.apache.poi.ss.usermodel.BorderStyle;
import org.apache.poi.ss.usermodel.HorizontalAlignment;
import org.apache.poi.ss.usermodel.VerticalAlignment;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.io.UnsupportedEncodingException;
import java.net.URLEncoder;
import java.util.*;
import java.util.concurrent.CompletableFuture;

/**
 * @ClassName
 * @Author niujie
 * @Version
 * @Description
 * @CreateTime 2023/3/5
 */
@Api(tags = "easyExcel 导出")
@RestController
@RequestMapping("/easyExcel")
public class EasyExcelController {

    @ApiOperation(value = "导出会员")
    @GetMapping("/exportMemberList")
    public void exportMemberList(HttpServletResponse response) throws IOException {
        setExcelRespProp(response, "会员列表");

        ExcelWriter writer = EasyExcel.write(response.getOutputStream(), Member.class).build();

        Map<Integer, CompletableFuture<List<Member>>> futures = new HashMap<>();
        for (int i = 1; i < 4; i++) {
            int finalI = i;
            CompletableFuture<List<Member>> future = CompletableFuture.supplyAsync(() -> {
                return getMemberList(finalI);
            }).whenComplete((r, ex) -> {
                if (ex != null) {
                    ex.printStackTrace();
                }
            });
            futures.put(finalI, future);
        }
        futures.keySet().forEach(key -> {
            List<Member> memberList = futures.get(key).join();
            WriteSheet sheet = EasyExcel.writerSheet(key, "第" + key + "页").build();
            writer.write(memberList, sheet);
        });

        writer.finish();
    }

    public List<Member> getMemberList(int page) {
        List<Member> memberList = new ArrayList<>();
        if (page == 1) {
            memberList.add(new Member(10L, "张三", "123456", "张三尼", new Date(),
                    "15618291111", 1));
            memberList.add(new Member(11L, "李四", "123456", "利利", new Date(),
                    "15618298639", 0));
        }
        if (page == 2) {
            memberList.add(new Member(10L, "张三2", "1234560", "张三尼-1", new Date(),
                    "15618292222", 1));
            memberList.add(new Member(11L, "李四2", "1234560", "利利-1", new Date(),
                    "15618298639", 0));
        }
        if (page == 3) {
            memberList.add(new Member(10L, "张三3", "1234567890", "张三尼-2", new Date(),
                    "1561829000", 1));
            memberList.add(new Member(11L, "李四3", "1234567890", "利利-2", new Date(),
                    "15618298600", 0));
        }
        return memberList;
    }

    @ApiOperation(value = "导出订单列表Excel")
    @GetMapping(value = "/exportOrderList")
    public void exportOrderList(HttpServletResponse response) throws IOException {

        List<OrderData> orderDataList = convert();
        setExcelRespProp(response, "订单列表");
        EasyExcel.write(response.getOutputStream())
                .head(OrderData.class)
                .registerWriteHandler(new CustomMergeStrategy(OrderData.class))
                .sheet("订单列表")
                .doWrite(orderDataList);
    }

    private List<OrderData> convert() {
        List<OrderData> result = new ArrayList<>();
        OrderData odOne = new OrderData();
        for (int i = 0; i < 3; i++) {
            odOne.setId("1001");
            odOne.setOrderSn("1001-1001-1002");
            odOne.setReceiverAddress("南京");
            odOne.setProductSn("100" + i);
            odOne.setName("海飞丝" + i);
            result.add(odOne);
        }


        OrderData odTwo = new OrderData();
        for (int i = 0; i < 2; i++) {
            odTwo.setId("1002");
            odTwo.setOrderSn("1002-1001-1002");
            odTwo.setReceiverAddress("上海");
            odTwo.setProductSn("100" + i);
            odTwo.setName("清扬" + i);
            result.add(odTwo);
        }


        return result;
    }

    /**
     * 设置excel下载响应头属性
     */
    private void setExcelRespProp(HttpServletResponse response, String rawFileName) throws UnsupportedEncodingException {
        response.setContentType("application/vnd.openxmlformats-officedocument.spreadsheetml.sheet");
        response.setCharacterEncoding("utf-8");
        String fileName = URLEncoder.encode(rawFileName, "UTF-8").replaceAll("\\+", "%20");
        response.setHeader("Content-disposition", "attachment;filename*=utf-8''" + fileName + ".xlsx");
    }

    public List<PileCheckMonthDto> checkList() {
        List<PileCheckMonthDto> pileList = new ArrayList<>();
        PileCheckMonthDto dto = new PileCheckMonthDto();
        dto.setId("1");
        dto.setCityid("101");
        dto.setDistrictid("1011");
        dto.setOrderNum("0001");
        dto.setName("学习");
        dto.setAddress("南京南站");
        dto.setAreastr("40000");
        dto.setHeightstr("30");
        dto.setStocknum("100");
        pileList.add(dto);

        return pileList;
    }

    @GetMapping("/exportStatics")
    public void statics(HttpServletResponse response) throws IOException {

        List<PileCheckMonthDto> pilebodysList = checkList();

        //设置序号
        for (int i = 1;i <= pilebodysList.size();i++){
            pilebodysList.get(i-1).setOrderNum(i+"");
        }

        response.setContentType("application/vnd.ms-excel");
        response.setCharacterEncoding("utf-8");
        // 这里URLEncoder.encode可以防止中文乱码 当然和easyexcel没有关系
        String fileName = URLEncoder.encode("存量建筑垃圾堆体治理进度月报表", "UTF-8");
        response.setHeader("Content-disposition",  "attachment;filename=" + fileName + ".xls");
        //内容样式策略
        WriteCellStyle contentWriteCellStyle = new WriteCellStyle();
        //垂直居中,水平居中
        contentWriteCellStyle.setVerticalAlignment(VerticalAlignment.CENTER);
        contentWriteCellStyle.setHorizontalAlignment(HorizontalAlignment.CENTER);
        contentWriteCellStyle.setBorderLeft(BorderStyle.THIN);
        contentWriteCellStyle.setBorderTop(BorderStyle.THIN);
        contentWriteCellStyle.setBorderRight(BorderStyle.THIN);
        contentWriteCellStyle.setBorderBottom(BorderStyle.THIN);
        //设置 自动换行
        contentWriteCellStyle.setWrapped(true);
        // 字体策略
        WriteFont contentWriteFont = new WriteFont();
        // 字体大小
        contentWriteFont.setFontHeightInPoints((short) 12);
        contentWriteCellStyle.setWriteFont(contentWriteFont);
        //头策略使用默认
        WriteCellStyle headWriteCellStyle = new WriteCellStyle();

        //excel如需下载到本地,只需要将response.getOutputStream()换成File即可(注释掉以上response代码)
        EasyExcel.write(response.getOutputStream(), PileCheckMonthDto.class)
                //设置输出excel版本,不设置默认为xlsx
                .excelType(ExcelTypeEnum.XLS).head(PileCheckMonthDto.class)
                //设置拦截器或自定义样式
                .registerWriteHandler(new MonthSheetWriteHandler())
                .registerWriteHandler(new HorizontalCellStyleStrategy(headWriteCellStyle, contentWriteCellStyle))
                .sheet("存量建筑垃圾堆体治理进度月报表")
                //设置默认样式及写入头信息开始的行数
                .useDefaultStyle(true).relativeHeadRowIndex(3)
                .doWrite(pilebodysList);
    }
}
